const fs = require('fs');
const path = require('path');
var mime = require('mime-types')
const s3Client = require('./s3Client');
const s3 = s3Client;


// 列出所有bucket
async function listBuckets() {
  try {
    const result = await s3.listBuckets().promise();
    console.log('Buckets:', result.Buckets);
    return result.Buckets;
  } catch (error) {
    console.error('Error listing buckets:', error);
    throw error;
  }
}

// 列出bucket中的对象
async function listObjects(bucketName) {
  try {
    const result = await s3.listObjects({ Bucket: bucketName }).promise();
    console.log('Objects in', bucketName, ':', result.Contents);
    return result.Contents;
  } catch (error) {
    console.error('Error listing objects:', error);
    throw error;
  }
}

// 生成预签名URL用于读取对象
async function generatePresignedUrl(bucketName, key, expires = 3600) {
  try {
    const url = await s3.getSignedUrlPromise('getObject', {
      Bucket: bucketName,
      Key: key,
      Expires: expires
    });
    console.log('Presigned URL:', url);
    return url;
  } catch (error) {
    console.error('Error generating presigned URL:', error);
    throw error;
  }
}

// 上传文件
// 上传文件
async function uploadFile(bucketName, filePath, key, options = {}) {
  try {
    // 确保文件存在
    if (!fs.existsSync(filePath)) {
      throw new Error(`File not found: ${filePath}`);
    }

    key = key.replace(/\\/g, '/');

    // 创建文件读取流（改用流式操作）
    const fileStream = fs.createReadStream(filePath);
    console.log('filePath',filePath, key, mime.lookup(filePath));

    // const body = await fs.readFile(filePath);

    // 设置默认参数
    const defaultParams = {
      Bucket: bucketName,
      Key: key,
      Body: fileStream, // 使用流作为Body
      // 默认使用mime类型检测（基于文件扩展名），否则回退到application/octet-stream
      ContentType: options.ContentType || mime.lookup(filePath) || 'application/octet-stream',
      // 添加缓存控制默认值
      CacheControl: options.CacheControl || 'max-age=3600',
      // 如果未指定存储类别，使用默认
      StorageClass: options.StorageClass || 'STANDARD'
    };

    // 合并用户提供的参数和默认参数
    const uploadParams = { ...defaultParams, ...options };

    const result = await s3.putObject(uploadParams).promise()
      .then(e => {
        console.log(`File uploaded successfully: ${key} `, e);
        return e;
      });

    return result;
  } catch (error) {
    console.error('Error uploading file:', error);
    throw error;
  }
}

// 删除文件
async function deleteFile(bucketName, key) {
  try {
    const result = await s3.deleteObject({
      Bucket: bucketName,
      Key: key
    }).promise();

    console.log(`File deleted successfully: ${key}`);
    return result;
  } catch (error) {
    console.error('Error deleting file:', error);
    throw error;
  }
}

// 递归读取文件夹中的所有文件
function getAllFiles(dirPath) {
  const files = [];
  const entries = fs.readdirSync(dirPath, { withFileTypes: true });

  for (const entry of entries) {
    const fullPath = path.join(dirPath, entry.name);
    if (entry.isDirectory()) {
      files.push(...getAllFiles(fullPath));
    } else {
      files.push(fullPath);
    }
  }

  return files;
}

// 同步本地文件夹到bucket
async function syncFolder(bucketName, folderPath, prefix = '') {
  try {
    const files = getAllFiles(folderPath);
    const uploadPromises = files.map(filePath => {
      // 计算相对路径作为key
      const relativePath = path.relative(folderPath, filePath);
      const key = prefix ? `${prefix}/${relativePath}` : relativePath;
      console.log('relativePath', relativePath);
      return uploadFile(bucketName, filePath, key);

    });

    await Promise.all(uploadPromises);
    console.log(`Folder synced successfully: ${folderPath}`);
    return { success: true, filesCount: files.length };
  } catch (error) {
    console.error('Error syncing folder:', error);
    throw error;
  }
}

// 创建桶
async function createBucket(bucketName) {
  try {
    const result = await s3.createBucket({ Bucket: bucketName }).promise().then(e=>{
        console.log(`Bucket created successfully: ${bucketName}`, e);

    });
    // console.log(`Bucket created successfully: ${bucketName}`);
    return result;
  } catch (error) {
    console.error('Error creating bucket:', error);
    throw error;
  }
}

// 删除桶
async function deleteBucket(bucketName) {
  try {
    // 首先确保桶为空
    const objects = await listObjects(bucketName);
    if (objects.length > 0) {
      console.warn(`Bucket ${bucketName} is not empty. Deleting all objects first...`);
      // 批量删除对象
      const deleteParams = {
        Bucket: bucketName,
        Delete: {
          Objects: objects.map(obj => ({ Key: obj.Key }))
        }
      };
      await s3.deleteObjects(deleteParams).promise();
      console.log(`All objects in ${bucketName} deleted successfully`);
    }

    // 然后删除桶
    const result = await s3.deleteBucket({ Bucket: bucketName }).promise();
    console.log(`Bucket deleted successfully: ${bucketName}`);
    return result;
  } catch (error) {
    console.error('Error deleting bucket:', error);
    throw error;
  }
}

// 删除文件夹(前缀)
async function deleteFolder(bucketName, prefix) {
  try {
    // 确保前缀以斜杠结尾
    if (!prefix.endsWith('/')) {
      prefix = `${prefix}/`;
    }

    // 列出所有带有该前缀的对象
    const result = await s3.listObjects({
      Bucket: bucketName,
      Prefix: prefix
    }).promise();

    if (result.Contents.length === 0) {
      console.log(`No objects found with prefix: ${prefix}`);
      return { success: true, deletedCount: 0 };
    }

    // 批量删除对象
    const deleteParams = {
      Bucket: bucketName,
      Delete: {
        Objects: result.Contents.map(obj => ({ Key: obj.Key }))
      }
    };

    await s3.deleteObjects(deleteParams).promise();
    console.log(`Deleted ${result.Contents.length} objects with prefix: ${prefix}`);
    return { success: true, deletedCount: result.Contents.length };
  } catch (error) {
    console.error('Error deleting folder:', error);
    throw error;
  }
}

module.exports = {
  listBuckets,
  listObjects,
  generatePresignedUrl,
  uploadFile,
  deleteFile,
  syncFolder,
  createBucket,
  deleteBucket,
  deleteFolder
};